// ==UserScript==
// @name           Yahoo Sports Player Info Popup
// @namespace      http://glenncarr.com/greasemonkey/yahoosports
// @include        http://*sports.yahoo.com/*
// @author         Glenn Carr (glenn at glenncarr dot com)
// $LastChangedRevision: 161 $
// $LastChangedDate: 2007-07-02 17:40:03 +0000 (Mon, 02 Jul 2007) $
// ==/UserScript==

(function(){

var YAHOO, yua, yud, yue, yut;

String.prototype.trim = function () {
  return this.replace(/^\s*(\S*(\s+\S+)*)\s*$/, "$1");
}

String.prototype.stripTags = function() {
  return this.replace(/<\/?[^>]+>/gi,'');
}

var PlayerInfo = function() {

    var cache = {};
    var POPUP_LINK_IMG = "%2BAC5%2FkfN%2F13T%" + 
"2F6no%2F8nw%2F%2F%2F%2F%2F%2F%2F%2F%2FwAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA" + 
"CH5BAMAAAsALAAAAAANAAoAAAhQAA0IHEhwgUEDCRIqTICAgMEFCA8cKECRgAAADyNSLEDAIsaDCTZ" + 
"2HHAxY0iOBAaQ%2FAgxZEcDHQGwRDiSQIEBLFsK2AkA58ODBAIIDZDTYEAAOw%3D%3D";
    var WORKING_IMG_URL = "data:image/gif,GIF89a%0A%00%0A%00%91%03%00%CC%CC%CC%FFff%FF%00%00%FF%FF%FF!%FF%" +
"0BNETSCAPE2.0%03%01%00%00%00!%F9%04%05%00%00%03%00%2C%00%00%00%00%0A%00%0A%00%00%02%17%9C'r%06%80%1A%" +
"02s'%AE%3Bqk%9A%E2%C3%81%14Gz%D9Q%00%00!%F9%04%05%00%00%03%00%2C%01%00%00%00%08%00%03%00%00%02%0A%9C%" +
"136%22%83%03%00S%10%14%00!%F9%04%05%00%00%03%00%2C%00%00%00%00%06%00%06%00%00%02%0C%9C%070%11%A8%7C%A" +
"2%11%22%D2X%00%00!%F9%04%05%00%00%03%00%2C%00%00%01%00%03%00%08%00%00%02%0A%1C%608%13%C1%BE%96%10c%16" +
"%00!%F9%04%05%00%00%03%00%2C%00%00%04%00%06%00%06%00%00%02%0A%04%86c%C9%1C%E1%A0%10l%16%00!%F9%04%05%" +
"00%00%03%00%2C%01%00%07%00%08%00%03%00%00%02%0A%04%86%23b%13%A1Dz%A9%00%00!%F9%04%05%00%00%03%00%2C%0" +
"4%00%04%00%06%00%06%00%00%02%0C%9C'r%A8%BB%11%06%00%03Jz%0A%00!%F9%04%09%00%00%03%00%2C%07%00%01%00%0" +
"3%00%08%00%00%02%0A%94f%A3%1A1%BD%00%18r%14%00%3B";

return {

    init: function() {
        this.inject();

        // Create custom events.
        this.onPlayerInfoReceived = new yut.CustomEvent('playerInfoReceived', this);

        var playerLinks = document.evaluate(
            "//*[contains(@href, 'http://sports.yahoo.com/mlb/players/')]",
            document,
            null,
            XPathResult.UNORDERED_NODE_SNAPSHOT_TYPE,
            null);

        for ( var i = 0; i < playerLinks.snapshotLength; i++) 
        {
            var playerLink = playerLinks.snapshotItem( i );
            if ( /\/players\/\d+$/i.test( playerLink.href ) )
            {
                var popupLink = document.createElement( 'a' );
                popupLink.setAttribute( "href", "#" );
                popupLink.setAttribute( "title", "Quick Player Info" );

                popupLink.innerHTML = "<img border=\"0\" src=\"" + POPUP_LINK_IMG +"\" />";
                playerLink.parentNode.insertBefore( popupLink, playerLink.nextSibling.nextSibling );
                yue.addListener(popupLink, 'click', this.showPlayerInfo, this, true);
            }
        }

      this.onPlayerInfoReceived.subscribe(function (e, args) {
        this.refreshInfo(args[0]);
      }, this, true);
    },
    
    showPlayerInfo: function (e) {
        e.preventDefault();
        var playerInfoPage = yud.get('playerinfodesc');
        var noteLink = yue.getTarget(e).parentNode.previousSibling.previousSibling;

        playerInfoPage.innerHTML = '<div class="loading">Loading...<img align="absmiddle" src="' + WORKING_IMG_URL + '"/></div>';
        yud.setStyle(playerInfoPage, 'display', 'block');
        yud.setXY(playerInfoPage, [yud.getX(noteLink) + noteLink.offsetWidth + 50, yud.getY(noteLink) - noteLink.offsetHeight]);
        
        PlayerInfo.getPlayerInfo( noteLink.href );
    },

    getPlayerInfo: function (url) {
      if (cache.hasOwnProperty(url)) {
        this.onPlayerInfoReceived.fire(cache[url]);
        return;
      }

      GM_xmlhttpRequest({
        method: 'GET',
        url   : url,
        onload: function (response) {
          cache[url] = response.responseText;
          PlayerInfo.onPlayerInfoReceived.fire(response.responseText);
        }
      });
    },

    refreshInfo: function (playerInfoContent) {
      var playerInfoPage = yud.get('playerinfodesc');
      
      var info = document.createElement( 'div' );
      info.innerHTML = playerInfoContent;
      var tables = info.getElementsByTagName( 'table' );
      var notes = new Array();
      for ( var i = 0; i < tables.length; i++ )
      {
        var table = tables[ i ];
        if ( table.getAttribute( 'class' ) == 'ysptblclbg3' )
        {
            var f = table.getElementsByTagName( 'form' )[ 0 ];
            f.parentNode.removeChild( f );
            var s = table.getElementsByTagName( 'script' )[ 0 ];
            s.parentNode.removeChild( s );
            notes.push( '<table class="ysptblclbg3" cellpadding="0">' + table.innerHTML + '</table>' );
        }
        if ( /^(&nbsp;)?last \d+ games/i.test( table.rows[ 0 ].cells[ 0 ].innerHTML ) )
        {
            notes.push( '<hr/><table cellpadding="0">' + table.innerHTML + '</table>' );
        }
      }
      if ( notes.length > 0 )
      {
        playerInfoPage.innerHTML = '<div class="inner">' + notes.join( '' ) + '</div>';
        return;
      }

      playerInfoPage.innerHTML = '<div class="inner">No notes.</div>';
    },

    inject: function() {
      GM_addStyle(
          '.playerinfopopup { text-align:left; float:left; margin:10px 0 0 10px !important; margin:10px 0 0 5px; width:500px; background: url(http://us.i1.yimg.com/us.yimg.com/i/us/sp/fn/default/full/drop_shadow.gif) no-repeat bottom right; }' +
          '.playerinfopopup p { margin-top: 3px; }' +
          '.playerinfopopup p:first-child { margin-top: 0; }' +
          '.playerinfopopup p:last-child { margin-bottom: 0; }' +
          '.playerinfopopup div.inner, .playerinfopopup div.loading { display:block; position:relative; background:#ffffcc; border:1px solid #333333; margin:0px 4px 4px 0px; padding:4px }' +
          '.playerinfopopup div.inner table td { font-size: 11px; border-bottom: 1px solid #666666 }' +
          '.playerinfopopup div.inner table tr:last-child td { border-bottom-width: 0px }' +
          '.playerinfopopup div.inner table tr>td:last-child {display:none;}' +
          '.playerinfopopup div.loading { font-style: italic; color: #666666; font-size: 80% }'
      );

      var div = document.createElement( 'DIV' );
      div.id = 'playerinfodesc';
      div.style.display = 'none';
      div.style.height = '0px';
      div.setAttribute( 'class', 'playerinfopopup' );
      div.style.zIndex = 99;
      document.body.appendChild( div );
    },
    
    loadYUI: function () {
      var yuiDomEvent = document.createElement('script'),
          yuiAnim     = document.createElement('script');

      try {
        yuiDomEvent.src  = 'http://yui.yahooapis.com/2.2.2/build/yahoo-dom-event/yahoo-dom-event.js';
        yuiAnim.src      = 'http://yui.yahooapis.com/2.2.2/build/animation/animation-min.js';

        document.body.appendChild(yuiDomEvent);
        document.body.appendChild(yuiAnim);
      } catch ( e )
      { return; }

      var loadInterval = setInterval(function () {
        if (!unsafeWindow.YAHOO || !unsafeWindow.YAHOO.util.Anim) {
          return;
        }

        clearInterval(loadInterval);

        YAHOO = unsafeWindow.YAHOO;
        yut   = YAHOO.util;
        yua   = yut.Anim;
        yud   = yut.Dom;
        yue   = yut.Event;

        PlayerInfo.init();
      }, 50);
    }
  };
}();

PlayerInfo.loadYUI();
})();